﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Threading;
using System.Windows;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using Microsoft.Phone.Controls;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input.Touch;
using PCRemoteMobileVer;

namespace PCRemoteMobileVer
{
    public partial class GamePage : PhoneApplicationPage
    {
        ContentManager contentManager;
        GameTimer timer;
        SpriteBatch spriteBatch;
        private Texture2D screenShot;
        private GraphicsDevice graphicsDevice;
        private Cursor mouse;
        private BackgroundWorker takeImageWorker;
        private bool _isGettingScreenshot;
        private bool _isMouseDragging;
        private bool _isGetError;
        public GamePage()
        {
            InitializeComponent();

            // Get the content manager from the application
            contentManager = (Application.Current as App).Content;

            // Create a timer for this page
            timer = new GameTimer();
            timer.UpdateInterval = TimeSpan.FromTicks(333333);
            timer.Update += OnUpdate;
            timer.Draw += OnDraw;

            TouchPanel.EnabledGestures = GestureType.DoubleTap | GestureType.VerticalDrag;
        }

        public BitmapImage ByteArraytoBitmap(Byte[] byteArray)
        {
            MemoryStream stream = new MemoryStream(byteArray);
            BitmapImage bitmapImage = new BitmapImage();

            WriteableBitmap bitmap = new WriteableBitmap(800, 480);
            bitmap.SetSource(stream);
            
            bitmapImage.SetSource(stream);

            Texture2D t = Texture2D.FromStream(SharedGraphicsDeviceManager.Current.GraphicsDevice, stream, 800, 480,
                                               false);
            return bitmapImage;
        }

        protected override void OnNavigatedTo(NavigationEventArgs e)
        {
            // Set the sharing mode of the graphics device to turn on XNA rendering
            SharedGraphicsDeviceManager.Current.GraphicsDevice.SetSharingMode(true);
            graphicsDevice = SharedGraphicsDeviceManager.Current.GraphicsDevice;
            // Create a new SpriteBatch, which can be used to draw textures.
            spriteBatch = new SpriteBatch(SharedGraphicsDeviceManager.Current.GraphicsDevice);

            // TODO: use this.content to load your game content here
            MainPage.SendCommand("TAKESNAP");
            byte[] imageData = MainPage.client.ReceiveImage();
            if (imageData != null)
            {
                MemoryStream stream = new MemoryStream(imageData);
                screenShot = Texture2D.FromStream(SharedGraphicsDeviceManager.Current.GraphicsDevice, stream, 800, 480,
                                              false);
            }
            //Begin get screenshot
            _isGetError = false;
            takeImageWorker = new BackgroundWorker();
            takeImageWorker.DoWork += GetScreenshot;
            takeImageWorker.WorkerSupportsCancellation = true;
            takeImageWorker.RunWorkerAsync();
            mouse = new Cursor(contentManager);
            timer.Start();

            base.OnNavigatedTo(e);
        }

        private void GetScreenshot(object sender, DoWorkEventArgs e)
        {
            while (true)
            {
                if (_isMouseDragging)
                    continue;
                _isGettingScreenshot = true;
                MainPage.SendCommand("TAKESNAP");
                byte[] imageData = MainPage.client.ReceiveImage();
                if (imageData != null)
                {
                    MemoryStream stream = new MemoryStream(imageData);
                    screenShot = Texture2D.FromStream(SharedGraphicsDeviceManager.Current.GraphicsDevice, stream, 800,
                                                      480,
                                                      false);
                }
                else
                {
                    _isGetError = true;
                }
                _isGettingScreenshot = false;
                Thread.Sleep(100);
            }
        }

        protected override void OnNavigatedFrom(NavigationEventArgs e)
        {
            // Stop the timer
            timer.Stop();

            // Set the sharing mode of the graphics device to turn off XNA rendering
            SharedGraphicsDeviceManager.Current.GraphicsDevice.SetSharingMode(false);
            takeImageWorker.CancelAsync();
            base.OnNavigatedFrom(e);
        }

        /// <summary>
        /// Allows the page to run logic such as updating the world,
        /// checking for collisions, gathering input, and playing audio.
        /// </summary>
        private void OnUpdate(object sender, GameTimerEventArgs e)
        {
            //if (_isGetError)
            //{
            //    MessageBox.Show("Socket closed! Please check your connection!");
            //    NavigationService.GoBack();
            //    return;
            //}
            if (!_isGettingScreenshot)
                mouse.Update();
            if (mouse.state == PCRemoteMobileVer.Cursor.Statement.CLICK)
            {
                MainPage.SendCommand("MouseClick");
                mouse.state = PCRemoteMobileVer.Cursor.Statement.RELEASE;
                _isMouseDragging = false;
            }
            else if (mouse.state == PCRemoteMobileVer.Cursor.Statement.DRAG)
            {
                MainPage.SendCommand("MouseMove(" + mouse.Position + ")");
                _isMouseDragging = true;
            }
            if (TouchPanel.IsGestureAvailable)
            {
                GestureSample gestureSample = TouchPanel.ReadGesture();
                if (gestureSample.GestureType == GestureType.DoubleTap)
                {
                    MainPage.SendCommand("DOUBLECLICK");
                }
            }
        }

        /// <summary>
        /// Allows the page to draw itself.
        /// </summary>
        private void OnDraw(object sender, GameTimerEventArgs e)
        {
            //if (_isGetError)
            //{
            //    return;
            //}
            SharedGraphicsDeviceManager.Current.GraphicsDevice.Clear(Color.Black);
            spriteBatch.Begin();
            spriteBatch.Draw(screenShot, graphicsDevice.Viewport.Bounds, screenShot.Bounds, Color.White);
            mouse.Draw(spriteBatch);
            spriteBatch.End();
            // TODO: Add your drawing code here
        }

        private void openKeyboard(object sender, EventArgs e)
        {
            NavigationService.Navigate(new Uri("/KeyboardSimulator.xaml", UriKind.Relative));
        }
    }
}